package com.ybkj.chat.utils;

import android.util.Log;

import org.apache.commons.codec.binary.Base64;

import java.security.InvalidKeyException;
import java.security.NoSuchAlgorithmException;
import java.security.SecureRandom;

import javax.crypto.BadPaddingException;
import javax.crypto.Cipher;
import javax.crypto.IllegalBlockSizeException;
import javax.crypto.KeyGenerator;
import javax.crypto.NoSuchPaddingException;
import javax.crypto.SecretKey;
import javax.crypto.spec.SecretKeySpec;


public class AESUtil {


    public static final String KEY_ALGORITHM = "AES";
    public static final String ECB_CIPHER_ALGORITHM = "AES/ECB/PKCS5Padding";


    /**
     * 使用ECB模式进行加密。 加密过程三步走： 1. 传入算法，实例化一个加解密器 2. 传入加密模式和密钥，初始化一个加密器
     * 3.调用doFinal方法加密
     *
     * @param plainText 需要签名的字符串
     * @return 加密结果(BASE64编码)
     */
    public static String AesEcbEncode(String plainText, String key) {

        try {
            Cipher cipher = Cipher.getInstance(ECB_CIPHER_ALGORITHM);
            SecretKey secretKey = new SecretKeySpec(Base64.decodeBase64(key), KEY_ALGORITHM);
            cipher.init(Cipher.ENCRYPT_MODE, secretKey);
            return Base64.encodeBase64String(cipher.doFinal(plainText.getBytes()));
        } catch (NoSuchAlgorithmException | NoSuchPaddingException | InvalidKeyException | IllegalBlockSizeException
                | BadPaddingException e) {
            Log.e("加密失败，plainText={}", plainText, e);
        } catch (Exception e) {
            Log.e("其他错误，plainText={}", plainText, e);
        }
        return null;
    }

    /**
     * 使用ECB解密，三步走
     *
     * @param decodedText 经过base64编码过后的密文
     * @param key         秘钥 (BASE64编码)
     * @return
     */
    public static String AesEcbDecode(String decodedText, String key) {
        try {
            Cipher cipher = Cipher.getInstance(ECB_CIPHER_ALGORITHM);
            SecretKey secretKey = new SecretKeySpec(Base64.decodeBase64(key), KEY_ALGORITHM);
            cipher.init(Cipher.DECRYPT_MODE, secretKey);
            return new String(cipher.doFinal(Base64.decodeBase64(decodedText)));
        } catch (NoSuchAlgorithmException | NoSuchPaddingException | InvalidKeyException | IllegalBlockSizeException
                | BadPaddingException e) {
            Log.e("解密失败，decodedText={}", decodedText, e);
        } catch (Exception e) {
            Log.e("其他错误，decodedText={}", decodedText, e);
        }
        return null;

    }


    /**
     * 1.创建一个KeyGenerator 2.调用KeyGenerator.generateKey方法
     * 由于某些原因，这里只能是128，如果设置为256会报异常 因为某些国家的进口管制限制，Java发布的运行环境包中的加解密有一定的限制。
     * 比如默认不允许256位密钥的AES加解密，解决方法就是修改策略文件
     *
     * @return 秘钥 (BASE64编码)
     */
    public static String generateAESSecretKey() {
        KeyGenerator keyGenerator;
        try {
            keyGenerator = KeyGenerator.getInstance(KEY_ALGORITHM);
            return Base64.encodeBase64String(keyGenerator.generateKey().getEncoded());
        } catch (NoSuchAlgorithmException e) {
            Log.e("生成秘钥失败", e.toString());
        }
        return null;
    }

    public static SecretKey getKey(String strKey) {
        try {
            KeyGenerator generator = KeyGenerator.getInstance("AES");
            SecureRandom secureRandom = SecureRandom.getInstance("SHA1PRNG");
            secureRandom.setSeed(Base64.decodeBase64(strKey));
            generator.init(128, secureRandom);
            return generator.generateKey();
        } catch (Exception e) {
            Log.e("初始化密钥出现异常", e.toString());
        }
        return null;
    }
}
